/*******************************************************************************
 * Copyright (c) 2008, 2009 Fabio Mauro - Alberto Terraneo.
 * Permission is granted to copy, distribute and/or modify this document
 * under the terms of the GNU Free Documentation License, Version 1.2
 * or any later version published by the Free Software Foundation.
 *     
 * This program is distributed in the hope that it will be useful, 
 * but WITHOUT ANY WARRANTY; without even the implied 
 * warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  
 * See the GNU Free Documentation License for more details.
 *     
 * You should have received a copy of the GNU Free Documentation 
 * License along with this distribution; if not, send a email to authors:
 * aterraneo <at> users.sourceforge.net
 * bigmoby09 <at> users.sourceforge.net
 *******************************************************************************/
package it.blueocean.acanto.web.platform.components.feedback;

import java.io.Serializable;

import org.apache.wicket.AttributeModifier;
import org.apache.wicket.markup.html.basic.Label;
import org.apache.wicket.markup.html.form.FormComponent;
import org.apache.wicket.model.IModel;
import org.apache.wicket.model.Model;

/**
 * Label displaying feedback messages for FormComponents.
 * <p>
 * You can use this Label to show the error message near the actual
 * FormComponent, instead of in the FeedbackPanel It's safe to remove the
 * FeedbackPanel if you use this class for every FormComponent in your Form.
 * <p>
 * You can use this code under Apache 2.0 license, as long as you retain the
 * copyright messages.
 * 
 * Tested with Wicket 1.3.4
 * 
 * @author Daan, StuQ.nl
 */
public class FeedbackLabel extends Label
{
	private static final long serialVersionUID = -7647976005107669833L;

	/**
	 * Field component holds a reference to the {@link Component} this
	 * FeedbackLabel belongs to
	 */
	private FormComponent<?> component;

	/** Field text holds a model of the text to be shown in the FeedbackLabel */
	private IModel<String> text = null;

	/**
	 * Call this constructor if you just want to display the FeedbackMessage of
	 * the component
	 * 
	 * @param id
	 *            The non-null id of this component
	 * @param component
	 *            The {@link FormComponent} to show the FeedbackMessage for.
	 */
	public FeedbackLabel(String id, FormComponent<?> component)
	{
		super(id);
		this.component = component;
	}

	/**
	 * Call this constructor if you want to display a custom text
	 * 
	 * @param id
	 *            The non-null id of this component
	 * @param component
	 *            The {@link FormComponent} to show the custom text for.
	 * @param text
	 *            The custom text to show when the FormComponent has a
	 *            FeedbackMessage
	 */
	public FeedbackLabel(String id, FormComponent<?> component, String text)
	{
		this(id, component, new Model<String>(text));
	}

	/**
	 * Call this constructor if you want to display a custom model (for easy
	 * i18n)
	 * 
	 * @param id
	 *            The non-null id of this component
	 * @param component
	 *            The {@link FormComponent} to show the custom model for.
	 * @param iModel
	 *            The custom model to show when the {@link FormComponent} has a
	 *            FeedbackMessage
	 */
	public FeedbackLabel(String id, FormComponent<?> component, IModel<String> iModel)
	{
		super(id);
		this.component = component;
		this.text = iModel;
	}

	/**
	 * Set the content of this FeedbackLabel, depending on if the component has
	 * a FeedbackMessage.
	 * 
	 * The HTML class attribute will be filled with the error level of the
	 * feedback message. That way, you can easily style different messages
	 * differently. Examples:
	 * 
	 * class = "feedbacklabel INFO" class = "feedbacklabel ERROR" class =
	 * "feedbacklabel DEBUG" class = "feedbacklabel FATAL"
	 * 
	 * 
	 * @see Component
	 */
	@Override
	protected void onBeforeRender()
	{
		super.onBeforeRender();
		this.setDefaultModel(null);
		if(component.getFeedbackMessage() != null)
		{
			if(this.text != null)
			{
				this.setDefaultModel(text);
			}
			else
			{
				this.setDefaultModel(new Model<Serializable>(component.getFeedbackMessage().getMessage()));
			}

			this.add(new AttributeModifier("class", true, new Model<String>("feedbacklabel "
					+ component.getFeedbackMessage().getLevelAsString().toUpperCase())));
		}
		else
		{
			this.setDefaultModel(null);
		}
	}
}
